package com.project.quiktask.controller;

import static org.junit.Assert.assertTrue;

import java.io.FileNotFoundException;
import java.io.IOException;
import java.text.ParseException;
import java.util.Vector;

import com.project.quiktask.Task;
import com.project.quiktask.datastore.FileLoader;
import com.project.quiktask.datastore.FileStorer;
import com.project.quiktask.util.Result;
import com.project.quiktask.util.Variable;

/**
 * This class handles the deletion of tasks from the QuikTask Manager.
 * It supports deletion by: ID displayed of the task
 * 							Keyword in the task
 * 
 * @author M I Azima
 *
 */
public class DeleteHandler implements CommandHandler {
	Task taskToBeDeleted = new Task();
	Result feedback;
	Vector<Task> deletedTasks=new Vector<Task>();
	Vector<Task> taskContainer = new Vector<Task>();

	public DeleteHandler() {

	}

	public Result execute(String parameter) {
		Result loadFileResult = loadStorageFile();
		if (isFileLoadedSuccessfully(loadFileResult)) {
			Result feedbackResult = executeDeleteCommand(parameter);
			return feedbackResult;
		} else
			return loadFileResult;
	}

	@SuppressWarnings("finally")
	public Result loadStorageFile()	{
		try	{
			FileLoader loader = new FileLoader(Variable.STORAGE_FILE_NAME);
			taskContainer = loader.load();
			/*if(deletedTasks.size()>1){
				return new Result(Variable.MANY_TASKS_WITH_SAME_KEYWORD,deletedTasks);
			}else{
				newTask=deletedTasks.get(0);
			}*/
		} catch (FileNotFoundException e) {
			return new Result(Variable.FEEDBACK_ERROR_FILE_NOT_FOUND);
		} catch (IOException e) {
			return new Result(Variable.FEEDBACK_ERROR_GENERAL);
		} catch (ParseException e) {
			return new Result(Variable.FEEDBACK_ERROR_GENERAL);
		} finally {
			return new Result(Variable.FEEDBACK_SUCCESS_FILE_LOADED);
		}
	}

	public boolean isFileLoadedSuccessfully(Result result) {
		if (result.getFeedback() == Variable.FEEDBACK_SUCCESS_FILE_LOADED)
			return true;
		else
			return false;
	}

	public Result executeDeleteCommand(String parameter)	{
		if(isNumeric(parameter)){
			int id=Integer.parseInt(parameter);
			try {
				deleteTaskById(id);
			} catch (IOException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			} catch (ParseException e) {
				// TODO Auto-generated catch block
				e.printStackTrace();
			}
		}else{
		SearchHandler Search = new SearchHandler();
		deletedTasks = Search.searchByKeyword(parameter, taskContainer);
		if(deletedTasks.size()==0){
			return new Result(Variable.NO_TASK_FOUND+parameter);
		}
		if(deletedTasks.size()>1){
			return new Result(Variable.MANY_TASKS_WITH_SAME_KEYWORD,deletedTasks);
		}
		taskToBeDeleted=deletedTasks.get(0);
		for(int i=0;i<taskContainer.size();i++){
			if(taskToBeDeleted.equals(taskContainer.get(i))){
				taskContainer.remove(taskContainer.get(i));
			}
		}
		try {
			storeUpdatedTaskContainer();
		} catch (IOException e) {
			return new Result("Failed to open file");
		}
		}
		return new Result(Variable.DELETE_TASK_SUCCEEDED);
		/*taskToBeDeleted = searchForTask(parameter);
		deleteAndUpdateTaskContainer();
		storeUpdatedTaskContainer();
		return feedback;*/
	}

	public void storeUpdatedTaskContainer() throws IOException	{
		FileStorer storer=new FileStorer();
		storer.storeManyTask(taskContainer);
	}
	
	public void deleteTaskById(int id) throws IOException, ParseException {
		DeleteHandler handler=(DeleteHandler) Controller.undoStack.peek();
		Vector<Task> deletedTasks=handler.deletedTasks;
		taskToBeDeleted=deletedTasks.get(id-1);
		deleteOneTask(taskToBeDeleted);
	}
	
	public static void deleteOneTask(Task deletedTask) throws IOException, ParseException{
		FileLoader loader = new FileLoader(Variable.STORAGE_FILE_NAME);
		Vector<Task> taskContainer= loader.load();	
		for(int i=0;i<taskContainer.size();i++){
			if(taskContainer.get(i).equalTo(deletedTask)){
				taskContainer.remove(taskContainer.get(i));
			}
		}
		(new FileStorer()).storeManyTask(taskContainer);
	}

	public static boolean isNumeric(String str)  
	{  
	  try  
	  {  
	    Integer.parseInt(str);  
	  }  
	  catch(NumberFormatException nfe)  
	  {  
	    return false;  
	  }  
	  return true;  
	}
	
	public Result undo(){
		//add back newTask
		assertTrue(taskToBeDeleted!=null);
		assertTrue(taskToBeDeleted.getTaskDescription()!=null);
		try {
			(new FileStorer()).storeTask(taskToBeDeleted);
		} catch (IOException e) {
			e.printStackTrace();
		}
		return new Result(Variable.FEEDBACK_UNDO_DELETE+taskToBeDeleted.getTaskDescription());
	}

}
